<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
</head>

<body>
    <script>
        const PENDING = 'pending'
        const RESOLVED = 'resolved'
        const REJECTED = 'rejected'

        function Dog(execute) {
            var that = this
            this.state = PENDING
            this.value = undefined
            this.reason = undefined
            this.onResovledFn = []
            this.onRejectedFn = []

            function resolve(value) {
                    if (that.state == PENDING) {
                        that.state = RESOLVED
                        that.value = value
                        that.onResovledFn.forEach((f) => {
                            f(that.value)
                        })
                    }

            }

            function reject(reason) {
                    if (that.state == PENDING) {
                        that.state = REJECTED
                        that.reason = reason
                        that.onRejectedFn.forEach((f) => {
                            f(that.reason)
                        })
                    }

            }
            try {
                execute(resolve, reject)//new 的时候同步调用,在此函数中调用resolve改变状态
            } catch (e) {
                reject(e)
            }
        }
        Dog.prototype.then = function (onResovled, onRejected) {
            var state = this.state
            var that = this
            return new Dog((resolve, reject)=>{
                switch(state){
                    case PENDING:
                        that.onResovledFn.push(function () {
                            try {
                                onResovled(that.value)
                            } catch (e) {
                                reject(e)
                            }

                        })
                        // that.onRejectedFn.push(function () {
                        //     try {
                        //         onRejected(that.reason)
                        //     } catch (e) {
                        //         reject(e)
                        //     }

                        // })
                    break;
                    case RESOLVED:
                        try {
                            setTimeout(()=>{
                                
                                const result = onResovled(that.value);
                                if(result instanceof Dog){
                                    result.then(resolve, reject)
                                }else{
                                    resolve(result)
                                }
                                
                            })
                        } catch (error) {
                                    
                        }
                    break;
                    case REJECTED:
                    break;
                }
            })
            // switch (status) {
            //     case PENDING:
            //         dog = new Dog(function (resolve, reject) {
            //             this.onResovledFn.push(function () {
            //                 try {
            //                     onResovled(that.value)
            //                 } catch (e) {
            //                     reject(e)
            //                 }

            //             })
            //             this.onRejectedFn.push(function () {
            //                 try {
            //                     onRejected(that.reason)
            //                 } catch (e) {
            //                     reject(e)
            //                 }

            //             })
            //         })


            //         break;
            //     case RESOLVED:
            //         //状态为resolved标识执行成功，调用then方法中传入的‘成功回调函数’
            //         dog = new Dog(function (resolve, reject) {
            //             setTimeout(function () {
            //                 try {
            //                     const result = onResovled(that.value)
            //                 } catch (e) {
            //                     reject(e)
            //                 }

            //             })
            //         })


            //         break;
            //     case REJECTED:
            //         dog = new Dog(function (resolve, reject) {
            //             setTimeout(function () {
            //                 try {
            //                     onRejected(that.reason)
            //                 } catch (e) {
            //                     reject(e)
            //                 }

            //             })
            //         })


            //         break;
            // }
            //返回一个promise实例，这样可以一直 .then(resolve, reject) 下去
            // return dog;
        }
        Dog.resolve = function(value){
            if(value instanceof Dog){
                return value
            }else{
                return new Dog((resolve,reject)=>resolve(value))
            }
        }

        //例子：

        new Dog((resolve) => {
            resolve(666)
        }).then(res => {
            console.log(res)
            return 123
        }).then(res=>{
            console.log('..',res)
            return 456
        }).then(res=>{
            console.log('...',res)
        })
    </script>
</body>

</html>